物件導向、物件導向,常常聽到卻一知半解,
鐵人後面也會探討一下物件導向的設計模式,藉這個機會把一知半解的JS物件搞個清楚!
下面是跟著MDN-JavaScript object basics
上物件的筆記。當然是以我不懂和不熟的觀念筆記為主啦!
物件導向我的解釋(菜鳥版本),就是把要做的事情都拿來當作物件來做處理,
彼此呼叫、又彼此獨立。
現實生活中,我們本來就是一個一個獨立的物體,
不過物件導向讓我們把抽象的[流程]、[邏輯]也當作物件來處理。
不過JS的物件導向,和傳統的C++, JAVA還是略有不同。
未來寫到再來討論(?C++, JAVA???完全不在我的規劃中XDDD)
物件是一組資料和功能,(像一個DIY工具箱一樣!)
供我們使用。
物件可說是JS最重要的觀念之一,
畢竟我們平常就在使用JS內建的類別實例、物件。
例如:
//使用JS實例裡的split方法
myString.split(',');
//使用 document類別裡的方法
let myDiv = document.createElement('div');
創造物件和取值想必大家都很熟悉了:
const africaCountry = {
name: "Ghana"
}
console.log(africaCountry.name);
this是物件導向一個很重要的觀念,可以幫我們指回實例本身。
下面利用建構式創造人,呼叫時搭配new
建構式通常大寫命名。
function CreatePerson(name){
this.name = name
this.introduceSelf = function() {
console.log(`Hi! I'm ${this.name}.`);
}
}
const rachel = new CreatePerson('Rachel');
rachel.name; //rachel
rachel.introduceSelf(); //Hi! I'm Rachel
傳統的 物件導向 都是先定義類別,在建立物件實例之後(const something = new Something),將類型複製到此實例。
但 JS 不是用複製的方式,而是在實例與原本的物件之間設定連結 (原型鍊中的連結),順著原型鍊就能找到屬性與函式。
假設我們有以下物件:
const africaCountry = {
country: 'Rwanda',
info() {
console.log(`${this.country} is in eastern Africa.`);
}
}
在console裡面輸入africaCountry
會看到country, info以外的原型方法:
valueOf, toString...
其實就是繼承了JS的物件原型。
我們在Object上看到的所有方法,並不是所有都會被繼承,
有prototype
的才會被繼承,如Object.prototype.toLocaleString()
不能繼承的,如Object.assign
我們只能在Object本身使用。
當呼叫一個實例裡面的函式會屬性時,
瀏覽器會先檢查實例物件上有沒有可用的,沒有再往上他的原型找,再沒有再往上到Object原型找。
就是所謂的原型鍊。
如:
function CreateACountry(country){
this.country = country
this.info = function() {
console.log(`You are traveling to ${this.country}`);
}
}
const Rwanda = new CreateACountry('Rwanda');
Rwanda.info();
Rwanda.toString(); //會先從繼承的CreateACountry找有沒有可用的,沒有再往上Object找
物件被繼承後,才修改、添加原型上的方法或屬性,
一樣會被讀取到!
如:
function Person(first, last, age, gender, interests) {
// property and method definitions
};
var person1 = new Person('Tammi', 'Smith', 32, 'neutral', ['music', 'skiing', 'kickboxing']);
Person.prototype.farewell = function() {
alert(this.name.first + ' has left the building. Bye for now!');
}
但是 farewell() 函式仍可用於 person1 物件實例,其可用的功能已自動更新過。如此證明了我們之前對原型鍊的說明,
也代表瀏覽器會沿著鍊往上找「尚未於物件實例上定義的函式」,而非「複製到實例中的函式」。
shadowing這部份很有趣,在MDN中文版本上沒看到這個翻譯。
const myDate = new Date(1995, 11, 17);
console.log(myDate.getYear()); // 95
myDate.getYear = function() {
console.log('something else!')
};
myDate.getYear(); // 'something else!'
This should be predictable, given the description of the prototype chain.
When we call getYear() the browser first looks in myDate for a property with that name,
and only checks the prototype if myDate does not define it. So when we add getYear() to myDate, then the version in myDate is called. This is called "shadowing" the property.
這邊的shadowing可能解釋成偽裝、遮蔽,就是我們劫持了原型上的getYear
自己做了別的功能!因為瀏覽器會順著原型鍊往上查找,先從實例找起,就會先找到我們自己做的功能囉!
明天來看一下常用的原型鍊和物件方法。
環遊非洲第12天--迦納
前幾年爆紅的黑人抬棺舞,原來就來自西非的迦納!
其實不只是迦納,很多非洲國家的葬禮都辦得像個熱熱鬧鬧的節慶,大家們又唱又跳,甚至可以長達一週,陪伴往生的人走完最後一程。
不過抬棺舞蹈是2006年一個加纳少年所發明出來的舞蹈!
除了抬棺舞外,加纳的棺材(Fantasy coffin)也是世界有名,各種形狀都有,可以看到魚的形狀、飛機...隨你客製化!除了葬禮之外,值得注意的是,迦納這幾年都是外資的投資對象。
因為迦納地理位置優渥,接壤很多西非國家,產業發展也多元,除了自然資源、礦產資源豐厚,2017年更發現了新的油田(Jubilee Field),黃金、可可、石油是三大出口外匯產品。迦納的可可豆出口是世界第二,佔約20%,而黃金是繼南非非洲第二大。